#include <Arduino.h>
#include <WiFi.h>           // 引入WiFi库文件，用于连接WiFi网络
#include "WiFiAirlink.h"    // 引入WiFi库文件，用于连接WiFi网络
#include <Wire.h>           // 引入Wire库文件，用于I2C通信
#include <Adafruit_AHTX0.h> //AHT20
Adafruit_AHTX0 AHT;
char DEV_ChipID[16]; // 设备ID
void airlink();      // 声明airlink函数，用于连接MQTT服务器
uint8_t receivedData[16];
uint8_t Equipment_status_machine[10] = {0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x06, 0x02, 0x00, 0x01}; // 设备状态机，用于控制设备状态的数组
uint8_t Relay_state_machine[20] = {0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x06, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
uint8_t Relay_1_state_machine[10] = {0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x06, 0x02, 0x00, 0x00};
float Temperature;
float Humidity;
uint8_t key[4] = {0x00, 0x00, 0x00, 0x00};
uint16_t Temperature1;
uint16_t Humidity1;
void led_blink(int num)
{
  for (int i = 0; i < num; i++)
  {
    digitalWrite(10, HIGH);
    vTaskDelay(200);
    digitalWrite(10, LOW);
    vTaskDelay(200);
  }
}
void setup()
{
  Serial.begin(9600);
  Serial1.begin(9600, SERIAL_8N1, 18, 19); // 初始化串口1，设置波特率为9600, 数据位8, 无校验位, 停止位1, RX引脚为GPIO18, TX引脚为GPIO19
  Serial1.setTimeout(10);                  // 关键！修改readBytes的超时时间（原默认1000ms，改为10ms减少阻塞）
  pinMode(6, OUTPUT);
  pinMode(10, OUTPUT);
  Wire.begin(5, 4);
  AHT.begin();
  uint32_t chipId = 0;
  for (int i = 0; i < 17; i = i + 8)
  {
    chipId |= ((ESP.getEfuseMac() >> (40 - i)) & 0xff) << i;
  }
  snprintf(DEV_ChipID, 16, "SLKZ-%06X", chipId);
}

void loop()
{
  sensors_event_t humidity, temp;
  AHT.getEvent(&humidity, &temp);
  Temperature = temp.temperature - 0.86;
  Humidity = humidity.relative_humidity;
  if (Serial1.available() > 0)
  {
    Serial1.readBytes(receivedData, 16);
    switch (receivedData[0])
    {
    case 0x00:
      break;
    case 0x03:
      switch (receivedData[3])
      {
      case 0x01:
        if (receivedData[5])
        {
          digitalWrite(5, HIGH);
          key[0] = 0x01;
          Relay_1_state_machine[9] = key[0];
          Serial1.write(Relay_1_state_machine, sizeof(Relay_1_state_machine));
          led_blink(2);
        }
        else
        {
          digitalWrite(5, LOW);
          key[0] = 0x00;
          Relay_1_state_machine[9] = key[0];
          Serial1.write(Relay_1_state_machine, sizeof(Relay_1_state_machine));
          led_blink(2);
        }
        break;
      case 0x02:
        if (receivedData[5])
        {
          digitalWrite(5, HIGH);
          key[1] = 0x01;
          Relay_1_state_machine[9] = key[1];
          Serial1.write(Relay_1_state_machine, sizeof(Relay_1_state_machine));
          led_blink(2);
        }
        else
        {
          digitalWrite(5, LOW);
          key[1] = 0x00;
          Relay_1_state_machine[9] = key[1];
          Serial1.write(Relay_1_state_machine, sizeof(Relay_1_state_machine));
          led_blink(2);
        }
        break;
      case 0x03:
        if (receivedData[5])
        {
          digitalWrite(5, HIGH);
          key[2] = 0x01;
          Relay_1_state_machine[9] = key[2];
          Serial1.write(Relay_1_state_machine, sizeof(Relay_1_state_machine));
          led_blink(2);
        }
        else
        {
          digitalWrite(5, LOW);
          key[2] = 0x00;
          Relay_1_state_machine[9] = key[2];
          Serial1.write(Relay_1_state_machine, sizeof(Relay_1_state_machine));
          led_blink(2);
        }
        break;
      case 0x04:
        if (receivedData[5])
        {
          digitalWrite(5, HIGH);
          key[3] = 0x01;
          Relay_1_state_machine[9] = key[3];
          Serial1.write(Relay_1_state_machine, sizeof(Relay_1_state_machine));
          led_blink(2);
        }
        else
        {
          digitalWrite(5, LOW);
          key[3] = 0x00;
          Relay_1_state_machine[9] = key[3];
          Serial1.write(Relay_1_state_machine, sizeof(Relay_1_state_machine));
          led_blink(2);
        }
        break;
      case 0x07:
        airlink();
        esp_restart();
        break;
      }
      break;
    case 0x06:
      switch (receivedData[3])
      {
      case 0x00:
        Serial1.write(Equipment_status_machine, sizeof(Equipment_status_machine));
        led_blink(2);
        break;
      case 0x05:
        Temperature1 = Temperature * 100;
        Relay_state_machine[8] = Temperature1 & 0xFF;        // 低8位：0x33（二进制最后8位）
        Relay_state_machine[9] = (Temperature1 >> 8) & 0xFF; // 高8位：0x0B（右移8位后取最后8位）
        Humidity1 = Humidity * 100;
        Relay_state_machine[10] = Humidity1 & 0xFF;        // 低8位：0x33（二进制最后8位）
        Relay_state_machine[11] = (Humidity1 >> 8) & 0xFF; // 高8位：0x0B（右移8位后取最后8位）
        Serial1.write(Relay_state_machine, sizeof(Relay_state_machine));
        led_blink(2);
        break;
      case 0x06:
        Temperature1 = Temperature * 100;
        Relay_state_machine[8] = Temperature1 & 0xFF;        // 低8位：0x33（二进制最后8位）
        Relay_state_machine[9] = (Temperature1 >> 8) & 0xFF; // 高8位：0x0B（右移8位后取最后8位）
        Humidity1 = Humidity * 100;
        Relay_state_machine[10] = Humidity1 & 0xFF;        // 低8位：0x33（二进制最后8位）
        Relay_state_machine[11] = (Humidity1 >> 8) & 0xFF; // 高8位：0x0B（右移8位后取最后8位）
        Relay_state_machine[13] = key[0];
        Relay_state_machine[15] = key[1];
        Relay_state_machine[17] = key[2];
        Relay_state_machine[19] = key[3];
        Serial1.write(Relay_state_machine, sizeof(Relay_state_machine));
        led_blink(2);
        break;
      }
      break;
    }
  }
  for (int i = 0; i < 16; i++)
  {
    receivedData[i] = 0x00;
  }
}
void airlink()
{ // 新配网程序
  WiFiAirlink Airlink;
  Airlink.setDebugOutput(false);
  Airlink.setMinimumSignalQuality(30); // 只列出信号质量超过30%的SSID
  Airlink.setConfigPortalTimeout(60);  // 60秒不配网操作则退出
  Airlink.setConnectTimeout(30);
  Airlink.startConfigPortal(DEV_ChipID); // 强制开启配网AP
  vTaskDelay(100);
}